package com.hydra.framework.router.receiver;

import android.app.Activity;
import android.content.Intent;
import android.util.Log;

import com.hydra.framework.router.RouterIntent;
import com.hydra.framework.util.StringUtil;

import java.util.Comparator;

import static com.hydra.framework.router.JRouter.JROUTER_LOG_TAG;

/**
 * Created by Hydra on 2017/7/30.
 *
 */
public final class RouterReceiver {

    public static Comparator<RouterReceiver> sRouterReceiverComparator = new Comparator<RouterReceiver>() {
        @Override
        public int compare(RouterReceiver lhs, RouterReceiver rhs) {
            if (!lhs.mUrl.equals(rhs.mUrl)) {
                throw new IllegalArgumentException("only the same url can be compared");
            }

            if(lhs.mReceiverHashCode == rhs.mReceiverHashCode) {
                return 0;
            }

            return (rhs.mPriority > lhs.mPriority) ? 1 : (rhs.mPriority < lhs.mPriority ? -1
                    : (rhs.mReceiverHashCode > lhs.mReceiverHashCode ? 1
                    : (rhs.mReceiverHashCode < lhs.mReceiverHashCode ? -1 : 0)));
        }
    };

    private final Class<?> mReceiverClass;
    private final int mFlags;
    private final int mPriority;
    private final int mReceiverHashCode;
    //加上url这个字段可以保证一下全局唯一，其实在一个url下的routerReceiver比较可以不加这个字段的
    private final String mUrl;

    public RouterReceiver(String url, int priority, Class<?> receiverClass, int flags) {
        this.mPriority = priority;
        this.mReceiverClass = receiverClass;
        this.mFlags = flags;
        this.mUrl = url;

        mReceiverHashCode = StringUtil.combineStr(mReceiverClass.getName(), "::", mUrl).hashCode();
    }

    public void receive(RouterIntent routerIntent) {
        try {
            Intent intent = new Intent(routerIntent.from, mReceiverClass);

            intent.setFlags(routerIntent.intentFlags);
            intent.putExtras(routerIntent.bundle);

            if(routerIntent.from instanceof Activity) {
                Activity from = Activity.class.cast(routerIntent.from);

                if(routerIntent.isForResult) {
                    from.startActivityForResult(intent, routerIntent.requestCode);
                } else {
                    from.startActivity(intent);
                }

                if(routerIntent.exitAnim != -1 && routerIntent.enterAnim != -1) {
                    from.overridePendingTransition(routerIntent.enterAnim, routerIntent.exitAnim);
                }

                if(routerIntent.finish) {
                    from.finish();
                }
            } else {
                routerIntent.from.startActivity(intent);
            }
        } catch (Throwable e) {
            Log.e(JROUTER_LOG_TAG, "receive router intent failed : " + e.toString());
        }
    }

    @Override
    public boolean equals(Object obj) {
        if(obj == null || !(obj instanceof RouterReceiver)) {
            return false;
        }

        RouterReceiver other = (RouterReceiver) obj;

        return this.mUrl.equals(other.mUrl) && this.mReceiverClass == other.mReceiverClass;
    }

    Class<?> receiverClass() {
        return mReceiverClass;
    }

    @Override
    public int hashCode() {
        return mReceiverHashCode;
    }
}
